home *** CD-ROM | disk | FTP | other *** search
/ Inter.Net 55-1 / Inter.Net 55-1.iso / CBuilder / Setup / BCB / data.z / memory.h < prev    next >
Encoding:
C/C++ Source or Header  |  1998-02-09  |  24.1 KB  |  926 lines

  1. #if !defined(__USING_STD_NAMES__)
  2. #  if !defined(__MEM_H)
  3. #    include <mem.h>
  4. #  endif /* __MEM_H */
  5. #else /* __USING_STD_NAMES__ */
  6.  
  7. #ifndef __STD_MEMORY
  8. #define __STD_MEMORY
  9. #pragma option push -b -a4 -Vx- -Ve- -w-inl -w-aus -w-sig
  10.  
  11. /***************************************************************************
  12.  *
  13.  * memory - declarations for the Standard Library memory implementation
  14.  *
  15.  * $Id: memory,v 1.103 1996/11/05 18:53:24 smithey Exp $
  16.  *
  17.  ***************************************************************************
  18.  *
  19.  * Copyright (c) 1994
  20.  * Hewlett-Packard Company
  21.  *
  22.  * Permission to use, copy, modify, distribute and sell this software
  23.  * and its documentation for any purpose is hereby granted without fee,
  24.  * provided that the above copyright notice appear in all copies and
  25.  * that both that copyright notice and this permission notice appear
  26.  * in supporting documentation.  Hewlett-Packard Company makes no
  27.  * representations about the suitability of this software for any
  28.  * purpose.  It is provided "as is" without express or implied warranty.
  29.  *
  30.  *
  31.  ***************************************************************************
  32.  *
  33.  * (c) Copyright 1994, 1995 Rogue Wave Software, Inc.
  34.  * ALL RIGHTS RESERVED *
  35.  * The software and information contained herein are proprietary to, and
  36.  * comprise valuable trade secrets of, Rogue Wave Software, Inc., which
  37.  * intends to preserve as trade secrets such software and information.
  38.  * This software is furnished pursuant to a written license agreement and
  39.  * may be used, copied, transmitted, and stored only in accordance with
  40.  * the terms of such license and with the inclusion of the above copyright
  41.  * notice.  This software and information or any other copies thereof may
  42.  * not be provided or otherwise made available to any other person.
  43.  *
  44.  * Notwithstanding any other lease or license that may pertain to, or
  45.  * accompany the delivery of, this computer software and information, the
  46.  * rights of the Government regarding its use, reproduction and disclosure
  47.  * are as set forth in Section 52.227-19 of the FARS Computer
  48.  * Software-Restricted Rights clause.
  49.  *
  50.  * Use, duplication, or disclosure by the Government is subject to
  51.  * restrictions as set forth in subparagraph (c)(1)(ii) of the Rights in
  52.  * Technical Data and Computer Software clause at DFARS 252.227-7013.
  53.  * Contractor/Manufacturer is Rogue Wave Software, Inc.,
  54.  * P.O. Box 2328, Corvallis, Oregon 97339.
  55.  *
  56.  * This computer software and information is distributed with "restricted
  57.  * rights."  Use, duplication or disclosure is subject to restrictions as
  58.  * set forth in NASA FAR SUP 18-52.227-79 (April 1985) "Commercial
  59.  * Computer Software-Restricted Rights (April 1985)."  If the Clause at
  60.  * 18-52.227-74 "Rights in Data General" is specified in the contract,
  61.  * then the "Alternate III" clause applies.
  62.  *
  63.  **************************************************************************/ 
  64.  
  65. #include <stdcomp.h>
  66.  
  67. #ifndef _RWSTD_NO_NEW_HEADER
  68. #include <cstddef>
  69. #include <cstdlib>
  70. #include <cstdio>
  71. #include <climits>
  72. #else
  73. #include <stddef.h>
  74. #include <stdlib.h>
  75. #include <stdio.h>
  76. #include <limits.h>
  77.  
  78. #endif //_RWSTD_NO_NEW_HEADER
  79.  
  80. #ifndef _RWSTD_HEADER_REQUIRES_HPP
  81. #include <new>
  82. #include <iterator>
  83. #include <utility>
  84. #else
  85. #include <new.hpp>
  86. #include <iterator.hpp>
  87. #include <utility.hpp>
  88. #endif
  89.  
  90. #ifdef _RWSTD_MULTI_THREAD
  91. #include <rw/stdmutex.h>
  92. #endif
  93.  
  94. //
  95. // Turn off the warnings under the MSVC compiler that
  96. // say 'bool reserved for future use'
  97. //
  98. #ifdef _RWSTD_MSVC_BOOL_WARNING
  99. #pragma warning ( disable : 4237 )
  100. #endif
  101.  
  102. #ifdef _RWSTD_NO_NEW_DECL
  103. extern void _RWSTDExportFunc(*) operator new(size_t size, void* ptr);
  104. #endif
  105.  
  106. #ifdef _RWSTD_NO_NEW_HEADER
  107. #ifndef _RWSTD_HEADER_REQUIRES_HPP
  108. #include <exception>
  109. #else
  110. #include <exception.hpp>
  111. #endif
  112. #endif
  113.  
  114. #ifndef _RWSTD_NO_NAMESPACE
  115. namespace __rwstd {
  116. #endif
  117.  
  118. // Default buffer size for containers.
  119. template <class T, class size>
  120. inline size __rw_allocation_size(T*,size)
  121. {
  122.   return sizeof(T) >= 1024 ? 1 : 1024 / sizeof(T);
  123. }
  124.  
  125. #if defined(_RWSTD_NO_DESTROY_NONBUILTIN)
  126. template <class T> struct __FS : public T
  127. {
  128.     __FS() { ; }
  129.     //
  130.     // Calls destructor, but does not free the space.
  131.     //
  132.     void operator delete (void*) {;} 
  133. };
  134. #endif
  135.  
  136.  
  137. #ifdef __TURBOC__
  138. #pragma option -w-inl
  139. #endif
  140.  
  141. template <class T>
  142. inline void __destroy (T* pointer)
  143. {
  144. #if defined(_RWSTD_NO_DESTROY_NONBUILTIN)
  145.     delete (__FS<T>*) (pointer);
  146. #else
  147. #if defined(_RWSTD_EXPLICIT_SCOPE_DESTROY)
  148.     pointer->T::~T();
  149. #else
  150.     pointer->~T();
  151. #endif
  152. #endif
  153. }
  154.  
  155.  
  156. template <class T1, class T2>
  157. inline void __construct (T1* p, const T2& value)
  158. {
  159.     new (p) T1(value);
  160. }
  161.  
  162.  
  163. #if defined(_RWSTD_NO_DESTROY_BUILTIN) || defined(_RWSTD_NO_DESTROY_NONBUILTIN)
  164. //
  165. // Some specializations of STL destroy for builtin types.f
  166. //
  167. inline void __destroy (void*)             {;}
  168. inline void __destroy (char*)             {;}
  169. inline void __destroy (unsigned char*)    {;}
  170. inline void __destroy (short*)            {;}
  171. inline void __destroy (unsigned short*)   {;}
  172. inline void __destroy (int*)              {;}
  173. inline void __destroy (unsigned int*)     {;}
  174. inline void __destroy (long*)             {;}
  175. inline void __destroy (unsigned long*)    {;}
  176. inline void __destroy (float*)            {;}
  177. inline void __destroy (double*)           {;}
  178. inline void __destroy (void**)            {;}
  179. inline void __destroy (char**)            {;}
  180. inline void __destroy (unsigned char**)   {;}
  181. inline void __destroy (short**)           {;}
  182. inline void __destroy (unsigned short**)  {;}
  183. inline void __destroy (int**)             {;}
  184. inline void __destroy (unsigned int**)    {;}
  185. inline void __destroy (long**)            {;}
  186. inline void __destroy (unsigned long**)   {;}
  187. inline void __destroy (float**)           {;}
  188. inline void __destroy (double**)          {;}
  189. inline void __destroy (void***)           {;}
  190. inline void __destroy (char***)           {;}
  191. inline void __destroy (unsigned char***)  {;}
  192. inline void __destroy (short***)          {;}
  193. inline void __destroy (unsigned short***) {;}
  194. inline void __destroy (int***)            {;}
  195. inline void __destroy (unsigned int***)   {;}
  196. inline void __destroy (long***)           {;}
  197. inline void __destroy (unsigned long***)  {;}
  198. inline void __destroy (float***)          {;}
  199. inline void __destroy (double***)         {;}
  200. #ifndef _RWSTD_NO_BOOL
  201. inline void __destroy (bool*)             {;}
  202. inline void __destroy (bool**)            {;}
  203. inline void __destroy (bool***)           {;}
  204. #endif
  205. #ifndef _RWSTD_NO_LONGDOUBLE
  206. inline void __destroy (long double*)      {;}
  207. inline void __destroy (long double**)     {;}
  208. inline void __destroy (long double***)    {;}
  209. #endif 
  210. #ifndef _RWSTD_NO_OVERLOAD_WCHAR
  211. inline void __destroy (wchar_t*)          {;}
  212. inline void __destroy (wchar_t**)         {;}
  213. inline void __destroy (wchar_t***)        {;}
  214. #endif
  215. #endif /*_RWSTD_NO_DESTROY_BUILTIN || _RWSTD_NO_DESTROY_NONBUILTIN*/
  216.  
  217. extern const char _RWSTDExportFunc(*) rwse_OutOfRange;
  218.  
  219. #ifndef _RWSTD_NO_NAMESPACE
  220. } // __rwstd namespace
  221.  
  222. namespace std {
  223. #endif
  224.  
  225. //
  226. // Raw storage iterator.
  227. //
  228.  
  229. template <class OutputIterator, class T>
  230. class raw_storage_iterator : public output_iterator
  231. {
  232.   protected:
  233.     OutputIterator iter;
  234.  
  235.   public:
  236.     typedef OutputIterator iterator_type;
  237.     typedef T element_type;
  238.  
  239.     _EXPLICIT raw_storage_iterator (OutputIterator x) : iter(x) {}
  240.     raw_storage_iterator<OutputIterator, T>& operator* () { return *this; }
  241.     raw_storage_iterator<OutputIterator, T>& operator= (const T& element)
  242.     {
  243. #ifndef _RWSTD_NO_NAMESPACE
  244.        using namespace __rwstd;
  245. #endif
  246.        *iter = element;
  247.        return *this;
  248.     }
  249.     raw_storage_iterator<OutputIterator, T>& operator++ ()
  250.     {
  251.         ++iter; return *this;
  252.     }
  253.     raw_storage_iterator<OutputIterator, T> operator++ (int)
  254.     {
  255.         raw_storage_iterator<OutputIterator, T> tmp = *this;
  256.         ++iter;
  257.         return tmp;
  258.     }
  259. };
  260.  
  261.  
  262.  
  263. //
  264. // Memory handling primitives.
  265. //
  266.  
  267. template <class ForwardIterator> 
  268. _RWSTD_TRICKY_INLINE void destroy (ForwardIterator first, ForwardIterator last)
  269. {
  270.     while (first != last)
  271.     {
  272. #ifndef _RWSTD_NO_NAMESPACE
  273.        using namespace __rwstd;
  274. #endif
  275.        __destroy(first);
  276.        ++first;
  277.     }
  278. }
  279.  
  280. #ifdef _RWSTD_FAST_TEMP_BUF
  281.  
  282. #if defined(_RWSTD_SHARED_LIB) && !defined (_RWSTD_MULTI_THREAD)
  283. #error Cannot use fast temporary buffer in this configuration
  284. #endif
  285. #if defined(_RWSTDDLL) && defined (__WIN16__)
  286. #error Cannot use fast temporary buffer in this configuration
  287. #endif
  288.  
  289. #ifndef __stl_buffer_size
  290. #define __stl_buffer_size 16384  /* 16k */
  291. #endif
  292.  
  293. #ifndef _RWSTD_NO_NAMESPACE
  294. }
  295.  
  296. namespace __rwstd {
  297. #endif
  298.  
  299. extern char _RWSTDExport stl_temp_buffer[__stl_buffer_size];
  300.  
  301. #ifdef _RWSTD_MULTI_THREAD
  302. extern _RWSTDMutex _RWSTDExport stl_temp_buffer_mutex;
  303. extern bool       _RWSTDExport stl_temp_buffer_being_used;
  304. #endif
  305.  
  306. #ifndef _RWSTD_NO_NAMESPACE
  307. } // End of __rwstd namespace
  308.  
  309. namespace std {
  310. #endif
  311.  
  312. template <class T>
  313. #ifndef _RWSTD_NO_TEMPLATE_ON_RETURN_TYPE
  314. inline pair<T*, ptrdiff_t> get_temporary_buffer (ptrdiff_t len)
  315. #else
  316. inline pair<T*, ptrdiff_t> get_temporary_buffer (ptrdiff_t len, T*)
  317. #endif
  318. {
  319.     while (len > __stl_buffer_size / sizeof(T))
  320.     {
  321.       T* tmp = _RWSTD_STATIC_CAST(T*,(   ::operator new(_RWSTD_STATIC_CAST(unsigned int,len) * sizeof(T))));
  322.       if (tmp)
  323.         {
  324.             pair<T*, ptrdiff_t> result(tmp, len);
  325.             return result;
  326.         }
  327.         len = len / 2;
  328.     }
  329.     
  330. #ifdef _RWSTD_MULTI_THREAD
  331.     _RWSTDGuard guard(__RWSTD::stl_temp_buffer_mutex);
  332.  
  333.     if (__RWSTD::stl_temp_buffer_being_used)
  334.     {
  335.       T* tmp = _RWSTD_STATIC_CAST(T*,(   ::operator new(_RWSTD_STATIC_CAST(unsigned int,len) * sizeof(T))));
  336.       pair<T*,ptrdiff_t> result(tmp, len);
  337.       return result;
  338.     }
  339.     else
  340.     {
  341.         __RWSTD::stl_temp_buffer_being_used = true;
  342.         pair<T*, ptrdiff_t> result(_RWSTD_STATIC_CAST(T*,
  343.                _RWSTD_STATIC_CAST(void*,__RWSTD::stl_temp_buffer)), 
  344.                _RWSTD_STATIC_CAST(ptrdiff_t,(__stl_buffer_size / sizeof(T))));
  345.         return result;
  346.     }
  347. #else
  348.     pair<T*, ptrdiff_t> result(_RWSTD_STATIC_CAST(T*,
  349.                _RWSTD_STATIC_CAST(void*,__RWSTD::stl_temp_buffer)), 
  350.                _RWSTD_STATIC_CAST(ptrdiff_t,(__stl_buffer_size / sizeof(T))));
  351.     return result;
  352. #endif /*_RWSTD_MULTI_THREAD*/
  353. }
  354.  
  355. template <class T>
  356. inline void return_temporary_buffer (T* p)
  357. {
  358. #ifdef _RWSTD_MULTI_THREAD
  359.   _RWSTDGuard guard(__RWSTD::stl_temp_buffer_mutex);
  360.  
  361.   if (_RWSTD_STATIC_CAST(char*,
  362.       _RWSTD_STATIC_CAST(void*,p)) != __RWSTD::stl_temp_buffer) 
  363.       ::operator delete(p);
  364.   else
  365.       __RWSTD::stl_temp_buffer_being_used = false;
  366. #else
  367.   if (_RWSTD_STATIC_CAST(char*,
  368.       _RWSTD_STATIC_CAST(void*,p)) != __RWSTD::stl_temp_buffer) 
  369.      ::operator delete(p);
  370. #endif /*_RWSTD_MULTI_THREAD*/
  371. }
  372.  
  373. #else
  374.  
  375. template <class T>
  376. inline pair<T*, int> get_temporary_buffer (int len, T*)
  377. {
  378.   T* tmp = _RWSTD_STATIC_CAST(T*,(   ::operator new(_RWSTD_STATIC_CAST(unsigned int,len) * sizeof(T))));
  379.     pair<T*,int> result(tmp, len);
  380.     return result;
  381. }
  382.  
  383. template <class T>
  384. inline void return_temporary_buffer (T* p)
  385. {
  386.    ::operator delete(p);
  387. }
  388.  
  389. #ifndef _RWSTD_NO_ARG_MATCH
  390. template <class T>
  391. inline pair<T*, long> get_temporary_buffer (long len, T* p)
  392. {
  393.     if (len > INT_MAX/sizeof(T)) 
  394.         len = INT_MAX/sizeof(T);
  395.   pair<T*, int> tmp = get_temporary_buffer(_RWSTD_STATIC_CAST(int,len), p);
  396.   return pair<T*, long>(tmp.first, _RWSTD_STATIC_CAST(long,tmp.second));
  397. }
  398. #endif /* _RWSTD_NO_ARG_MATCH */
  399.  
  400. #endif /*_RWSTD_FAST_TEMP_BUF*/
  401.  
  402. //
  403. // The default allocator.
  404. //
  405.  
  406.  
  407. #ifdef _RWSTD_ALLOCATOR
  408.  
  409. template <class T> class allocator;
  410.  
  411. //
  412. // void specialization of allocator
  413. //
  414. _RWSTD_TEMPLATE
  415. class allocator<void> {  
  416.   public:
  417.     typedef void*       pointer;
  418.     typedef const void* const_pointer;
  419.     typedef void        value_type;
  420.    
  421.     template <class U> 
  422.     struct rebind { typedef allocator<U> other; };
  423.     
  424. #ifndef _RWSTD_NO_MULTI_DIM_ARRAY
  425.     ~allocator()  _RWSTD_THROW_SPEC_NULL
  426.     { ; }
  427. #endif
  428.  
  429. };
  430.  
  431.  
  432. template <class T>
  433. class allocator
  434. {
  435.   public:
  436.     typedef size_t     size_type;
  437.     typedef ptrdiff_t  difference_type;
  438.     typedef T*         pointer;
  439.     typedef const T*   const_pointer;
  440.     typedef T&         reference;
  441.     typedef const T&   const_reference;
  442.     typedef T          value_type;
  443.  
  444. #ifndef _RWSTD_NO_MEMBER_CLASS_TEMPLATES
  445.     template <class U> struct rebind
  446.     { typedef allocator<U> other; };
  447. #endif
  448.  
  449.     allocator()  _RWSTD_THROW_SPEC_NULL
  450.     { ; }
  451.  
  452.     template <class U>
  453.     allocator(const allocator<U>&)  _RWSTD_THROW_SPEC_NULL
  454.     { ; }
  455.     template <class U>
  456.     allocator<T>& operator=(const allocator<U>& a)  _RWSTD_THROW_SPEC_NULL
  457.     { return *this; }
  458.     
  459. #ifndef _RWSTD_NO_MULTI_DIM_ARRAY
  460.     ~allocator()  _RWSTD_THROW_SPEC_NULL
  461.     { ; }
  462. #endif
  463.  
  464.     pointer address(reference x) const
  465.     { 
  466.       return _RWSTD_STATIC_CAST(pointer,&x); 
  467.     }
  468.     const_pointer address(const_reference x) const
  469.     { 
  470.       return _RWSTD_STATIC_CAST(const_pointer,&x); 
  471.     }
  472.     pointer allocate(size_type n, 
  473.         _TYPENAME allocator<void>::const_pointer hint = 0)
  474.     { 
  475.       pointer tmp =
  476.          _RWSTD_STATIC_CAST(pointer,(::operator 
  477.             new(_RWSTD_STATIC_CAST(size_t,(n * sizeof(value_type))))));
  478.       _RWSTD_THROW_NO_MSG(tmp == 0, bad_alloc);
  479.       return tmp;
  480.     }
  481.  
  482.     void deallocate(pointer p, size_type) 
  483.     { 
  484.       ::operator delete(p);
  485.     }
  486.     size_type max_size() const  _RWSTD_THROW_SPEC_NULL
  487.     { 
  488.       return max(size_type(1), size_type(UINT_MAX/sizeof(T))); 
  489.     }
  490.     inline void construct(pointer p, const T& val);
  491.  
  492.     inline void destroy(T* p);
  493.  
  494. };
  495.  
  496.  
  497.  
  498. template <class T>
  499. void allocator<T>::construct(pointer p, const T& val)
  500. {
  501. #ifndef _RWSTD_NO_NAMESPACE
  502.   using namespace __rwstd;
  503. #endif
  504.   __construct(p,val);
  505. }
  506.  
  507. template <class T>
  508. void allocator<T>::destroy(T* p)
  509. {
  510. #ifndef _RWSTD_NO_NAMESPACE
  511.   using namespace __rwstd;
  512. #endif
  513.   __destroy(p);
  514. }
  515.  
  516. #else
  517.  
  518. //
  519. // Alternate allocator uses an interface class (allocator_interface)
  520. // to get type safety.
  521. //
  522. template <class T>
  523. class allocator
  524.  public:
  525.    
  526.     typedef size_t    size_type;
  527.     typedef ptrdiff_t difference_type;
  528.     typedef T*         pointer;
  529.     typedef const T*   const_pointer;
  530.     typedef T&         reference;
  531.     typedef const T&   const_reference;
  532.     typedef T          value_type;
  533.  
  534.     allocator()  _RWSTD_THROW_SPEC_NULL { ; }
  535.     allocator(const allocator<T>&)  _RWSTD_THROW_SPEC_NULL
  536.     { ; }
  537.     allocator<T>& operator=(const allocator<T>&)  _RWSTD_THROW_SPEC_NULL
  538.     { return *this; }
  539.  
  540. #ifndef _RWSTD_NO_MULTI_DIM_ARRAY
  541.     ~allocator()  _RWSTD_THROW_SPEC_NULL { ; }
  542. #endif
  543.  
  544.     void * allocate (size_type n, void *  = 0)
  545.     { 
  546.       void * tmp = _RWSTD_STATIC_CAST(void*,(::operator new(_RWSTD_STATIC_CAST(size_t,(n)))));
  547.       _RWSTD_THROW_NO_MSG(tmp == 0, bad_alloc);
  548.       return tmp;
  549.     }
  550.     
  551.     void deallocate (void* p, size_type) 
  552.     { 
  553.       ::operator delete(p);
  554.     }
  555.     size_type max_size (size_type size) const
  556.     { 
  557.       return 1 > UINT_MAX/size ? size_type(1) : size_type(UINT_MAX/size);
  558.     }
  559. };
  560.  
  561. _RWSTD_TEMPLATE
  562. class allocator<void>
  563.  public:
  564.    
  565.     typedef size_t    size_type;
  566.     typedef ptrdiff_t difference_type;
  567.     typedef void*         pointer;
  568.     typedef const void*   const_pointer;
  569.     typedef void          value_type;
  570.  
  571.     allocator() _RWSTD_THROW_SPEC_NULL { ; }
  572.     allocator(const allocator<void>&)  _RWSTD_THROW_SPEC_NULL
  573.     { ; }
  574.     allocator<void>& operator=(const allocator<void>&)  _RWSTD_THROW_SPEC_NULL
  575.     { return *this; }
  576. #ifndef _RWSTD_NO_MULTI_DIM_ARRAY
  577.     ~allocator() _RWSTD_THROW_SPEC_NULL { ; }
  578. #endif
  579.  
  580.     void * allocate (size_type n, void *  = 0)
  581.     { 
  582.       void * tmp = _RWSTD_STATIC_CAST(void*,(::operator new(_RWSTD_STATIC_CAST(size_t,(n)))));
  583.       _RWSTD_THROW_NO_MSG(tmp == 0, bad_alloc);
  584.       return tmp;
  585.     }
  586.     
  587.     void deallocate (void* p, size_type) 
  588.     { 
  589.       ::operator delete(p);
  590.     }
  591.     size_type max_size (size_type size) const
  592.     { 
  593.       return 1 > UINT_MAX/size ? size_type(1) : size_type(UINT_MAX/size);
  594.     }
  595. };
  596.  
  597. //
  598. // allocator_interface provides all types and typed functions.  Memory
  599. // allocated as raw bytes using the class provided by the Allocator
  600. // template parameter.  allocator_interface casts appropriately.
  601. //
  602. // Multiple allocator_interface objects can attach to a single 
  603. // allocator, thus allowing one allocator to allocate all storage
  604. // for a container, regardless of how many types are involved.
  605. //
  606. // The only real restriction is that pointer and reference are
  607. // hard coded as T* and T&.  Partial specialization would 
  608. // get around this.
  609. //
  610. template <class Allocator,class T>
  611. class allocator_interface 
  612. {
  613. public:
  614.   typedef Allocator allocator_type;
  615.   typedef T*         pointer;
  616.   typedef const T*   const_pointer;      
  617.   typedef T&         reference;
  618.   typedef const T&   const_reference;
  619.   typedef T          value_type;
  620.   typedef _TYPENAME _RWSTD_ALLOC_SIZE_TYPE             size_type;
  621.   typedef _TYPENAME _RWSTD_ALLOC_DIFF_TYPE             difference_type;
  622.   typedef void*      void_pointer;
  623.   typedef const void* const_void_pointer;
  624.  
  625.  
  626.  
  627. protected:
  628.   allocator_type         alloc_;
  629.  
  630. public:
  631.   allocator_interface()  _RWSTD_THROW_SPEC_NULL  { ; }
  632.   allocator_interface(const Allocator& a)  _RWSTD_THROW_SPEC_NULL
  633.    : alloc_(a) { ; }
  634.  
  635.   pointer address (T& x) 
  636.   { 
  637.     return _RWSTD_STATIC_CAST(pointer,&x); 
  638.   }
  639.   
  640.   size_type max_size ()  const
  641.   { 
  642.     return alloc_.max_size(sizeof(T));
  643.   }
  644.  
  645.   pointer allocate(size_type n, pointer  = 0)
  646.   {
  647.     return _RWSTD_STATIC_CAST(pointer,alloc_.allocate(n*sizeof(T)));
  648.   }
  649.  
  650.   void deallocate(pointer p, size_type n)
  651.   {
  652.     alloc_.deallocate(p,n);
  653.   }
  654.  
  655.   inline void construct(pointer p, const T& val);
  656.  
  657.   inline void destroy(T* p);
  658.  
  659. };
  660.  
  661.  
  662. template <class Allocator, class T>
  663. inline void 
  664. allocator_interface<Allocator,T>::construct(pointer p, const T& val)
  665. {
  666. #ifndef _RWSTD_NO_NAMESPACE
  667.   using namespace __rwstd;
  668. #endif
  669.   __construct(p,val);
  670. }
  671.  
  672. template <class Allocator, class T>
  673. inline void allocator_interface<Allocator,T>::destroy(T* p)
  674. {
  675. #ifndef _RWSTD_NO_NAMESPACE
  676.   using namespace __rwstd;
  677. #endif
  678.   __destroy(p);
  679. }
  680.  
  681. _RWSTD_TEMPLATE
  682. class allocator_interface<allocator<void>,void> 
  683. {
  684. public:
  685.   typedef allocator<void> allocator_type;
  686.   typedef void*         pointer;
  687.   typedef const void*   const_pointer;      
  688.   typedef void          value_type;
  689.   typedef allocator<void>::size_type       size_type;
  690.   typedef allocator<void>::difference_type difference_type;
  691.  
  692. protected:
  693.   allocator_type         alloc_;
  694.  
  695. public:
  696.   allocator_interface()  _RWSTD_THROW_SPEC_NULL { ; }
  697.   allocator_interface(const allocator<void>& a) _RWSTD_THROW_SPEC_NULL
  698.    : alloc_(a) { ; }
  699.  
  700.   size_type max_size ()  const
  701.   { 
  702.     return alloc_.max_size(1);
  703.   }
  704.  
  705.   pointer allocate(size_type n, pointer  = 0)
  706.   {
  707.     return _RWSTD_STATIC_CAST(pointer,alloc_.allocate(n));
  708.   }
  709.  
  710.   void deallocate(pointer p, size_type n)
  711.   {
  712.     alloc_.deallocate(p,n);
  713.   }      
  714. };
  715.  
  716.  
  717. #endif  // _RWSTD_ALLOCATOR
  718.  
  719. #ifndef _RWSTD_NO_NAMESPACE
  720. }
  721. #endif
  722.  
  723.  
  724. // 
  725. // allocator globals
  726. //
  727. #ifndef HPPA_WA
  728. template <class U>
  729. #ifndef _RWSTD_NO_NAMESPACE
  730. inline void * operator new(size_t N, std::allocator<U>& a)
  731. #else
  732. inline void * operator new(size_t N, allocator<U>& a)
  733. #endif
  734. {
  735.   return _RWSTD_STATIC_CAST(void*,a.allocate(N));
  736. }
  737.  
  738. #if !defined(_RWSTD_NO_NEW_BRACKETS)
  739. template <class U>
  740. #ifndef _RWSTD_NO_NAMESPACE
  741. inline void * operator new[](size_t N, std::allocator<U>& a)
  742. #else
  743. inline void * operator new[](size_t N, allocator<U>& a)
  744. #endif
  745. {
  746.   return _RWSTD_STATIC_CAST(void*,a.allocate(N*sizeof(U)));
  747. }
  748.  
  749. #ifndef _RWSTD_NO_NAMESPACE
  750. inline void * operator new[](size_t N, std::allocator<void>& a)
  751. #else
  752. inline void * operator new[](size_t N, allocator<void>& a)
  753. #endif
  754. {
  755.   return _RWSTD_STATIC_CAST(void*,a.allocate(N));
  756. }
  757.  
  758. template <class U>
  759. #ifndef _RWSTD_NO_NAMESPACE
  760. inline void operator delete(void* p, std::allocator<U>& a)
  761. #else
  762. inline void operator delete(void* p, allocator<U>& a)
  763. #endif
  764. {
  765.   a.deallocate(p);
  766. }
  767.  
  768. template <class U>
  769. #ifndef _RWSTD_NO_NAMESPACE
  770. inline void operator delete[](void* p, std::allocator<U>& a)
  771. #else
  772. inline void operator delete[](void* p, allocator<U>& a)
  773. #endif
  774. {
  775.   a.deallocate(p);
  776. }
  777. #endif /*(_RWSTD_NO_NEW_BRACKETS) */
  778. #endif /* HPPA_WA */
  779.  
  780. #ifndef _RWSTD_NO_NAMESPACE
  781. namespace std {
  782. #endif
  783.  
  784. template <class U>
  785. inline bool operator==(const allocator<U>&, const allocator<U>&)  _RWSTD_THROW_SPEC_NULL
  786. {
  787.   return true;
  788. }
  789.  
  790. #ifndef _RWSTD_NO_NAMESPACE
  791. template <class U>
  792. inline bool operator!=(const allocator<U>&, const allocator<U>&)  _RWSTD_THROW_SPEC_NULL
  793. {
  794.   return false;
  795. }
  796. #endif
  797.  
  798.  
  799. //
  800. // Specialized algorithms.
  801. //
  802.  
  803. template <class InputIterator, class ForwardIterator>
  804. _RWSTD_TRICKY_INLINE ForwardIterator uninitialized_copy (InputIterator first, InputIterator last,
  805.                                     ForwardIterator result)
  806. {
  807. #ifndef _RWSTD_NO_NAMESPACE
  808.     using namespace __rwstd;
  809. #endif
  810.     while (first != last) __construct(result++, *first++);
  811.     return result;
  812. }
  813.  
  814. template <class ForwardIterator, class T>
  815. _RWSTD_TRICKY_INLINE void uninitialized_fill (ForwardIterator first, ForwardIterator last,
  816.                          const T& x)
  817. {
  818. #ifndef _RWSTD_NO_NAMESPACE
  819.     using namespace __rwstd;
  820. #endif
  821.     while (first != last) __construct(first++, x);
  822. }
  823.  
  824. template <class ForwardIterator, class Size, class T>
  825. _RWSTD_TRICKY_INLINE void uninitialized_fill_n (ForwardIterator first, Size n, const T& x)
  826. {
  827. #ifndef _RWSTD_NO_NAMESPACE
  828.     using namespace __rwstd;
  829. #endif
  830.     while (n--) __construct(first++, x);
  831. }
  832.  
  833.  
  834. //
  835. // Template auto_ptr holds onto a pointer obtained via new and deletes that
  836. // object when it itself is destroyed (such as when leaving block scope).
  837. //
  838. // It can be used to make calls to new() exception safe.
  839. //
  840.  
  841. template<class X> class auto_ptr
  842. {
  843.   public:
  844.     typedef X element_type;
  845.  
  846.     //
  847.     // construct/copy/destroy
  848.     //
  849.     _EXPLICIT auto_ptr (X* p = 0)  _RWSTD_THROW_SPEC_NULL
  850.       : owner((bool)p), the_p(p)
  851.     { ; }
  852. #ifndef _RWSTD_NO_MEMBER_TEMPLATES
  853.     template <class Y>
  854.     auto_ptr (const auto_ptr<Y>& a)  _RWSTD_THROW_SPEC_NULL
  855.       : owner(a.owner), the_p((_RWSTD_CONST_CAST(auto_ptr<Y>&,a)).release()) 
  856.     { ; }
  857.     template <class Y>
  858.     auto_ptr<X>& operator= (const auto_ptr<Y>& rhs)  _RWSTD_THROW_SPEC_NULL
  859.     { 
  860.       if (the_p != rhs.get())
  861.       {
  862.         if (owner) 
  863.           delete the_p;
  864.         owner = rhs.owner;
  865.       }
  866.       else
  867.         owner = owner || rhs.owner ? true : false;
  868.       the_p = (_RWSTD_CONST_CAST(auto_ptr<Y>&,rhs)).release();
  869.       return *this;
  870.     }
  871. #else
  872.     auto_ptr (const auto_ptr<X>& a)  _RWSTD_THROW_SPEC_NULL
  873.       : owner(a.owner), the_p((_RWSTD_CONST_CAST(auto_ptr<X>&,a)).release()) 
  874.     { ; }
  875.     auto_ptr<X>& operator= (const auto_ptr<X>& rhs)  _RWSTD_THROW_SPEC_NULL
  876.     { 
  877.       if (the_p != rhs.get())
  878.       {
  879.         if (owner) 
  880.           delete the_p;
  881.         owner = rhs.owner;
  882.       }
  883.       else
  884.         owner = owner || rhs.owner ? true : false;
  885.       the_p = (_RWSTD_CONST_CAST(auto_ptr<X>&,rhs)).release(); 
  886.       return *this;
  887.     }
  888. #endif
  889.     ~auto_ptr () { if (owner) delete the_p; }
  890.     //
  891.     // members
  892.     //
  893.     X& operator*  ()  const _RWSTD_THROW_SPEC_NULL { return *the_p;   }
  894.     X* operator-> ()  const _RWSTD_THROW_SPEC_NULL { return the_p;    }
  895.     X* get        ()  const _RWSTD_THROW_SPEC_NULL { return the_p;    }
  896.     X* release    ()        
  897. #ifndef _RWSTD_NO_MUTABLE    
  898.       const
  899. #endif
  900.     _RWSTD_THROW_SPEC_NULL
  901.     { 
  902.       owner = false; 
  903.       return the_p; 
  904.     }
  905.  
  906.   
  907. private:
  908.  
  909. #ifdef _RWSTD_NO_MUTABLE    
  910.     bool owner;
  911. #else
  912.     _MUTABLE bool owner;
  913. #endif
  914.     X* the_p;
  915. };
  916.  
  917. #ifndef _RWSTD_NO_NAMESPACE
  918. }
  919. #endif
  920.  
  921. #pragma option pop
  922. #endif /*__STD_MEMORY*/
  923. #endif /* __USING_STD_NAMES__ && ! __MEM_H */
  924.